

-- -----------------------------------------------------------------------------
--  Abstract        : top level for the non-levelling AFI PHY sequencer
--                    The top level instances the sub-blocks of the AFI PHY
--                    sequencer. In addition a number of multiplexing and high-
--                    level control operations are performed. This includes the
--                    multiplexing and generation of control signals for: the
--                    address and command DRAM interface and pll, oct and datapath
--                    latency control signals.
-- -----------------------------------------------------------------------------

--altera message_off 10036

library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;

--
entity ddr2_phy_alt_mem_phy_seq_nocalib IS
    generic (
        -- choice of FPGA device family and DRAM type
        FAMILY                         : string;
        MEM_IF_MEMTYPE                 : string;
        SPEED_GRADE                    : string;
        FAMILYGROUP_ID                 : natural;

        -- physical interface width definitions
        MEM_IF_DQS_WIDTH               : natural;
        MEM_IF_DWIDTH                  : natural;
        MEM_IF_DM_WIDTH                : natural;
        MEM_IF_DQ_PER_DQS              : natural;
        DWIDTH_RATIO                   : natural;
        CLOCK_INDEX_WIDTH              : natural;
        MEM_IF_CLK_PAIR_COUNT          : natural;
        MEM_IF_ADDR_WIDTH              : natural;
        MEM_IF_BANKADDR_WIDTH          : natural;
        MEM_IF_CS_WIDTH                : natural;
        MEM_IF_NUM_RANKS               : natural;
        MEM_IF_RANKS_PER_SLOT          : natural;
        ADV_LAT_WIDTH                  : natural;
        RESYNCHRONISE_AVALON_DBG       : natural;  -- 0 = false, 1 = true
        AV_IF_ADDR_WIDTH               : natural;

        -- Not used for non-levelled seq
        CHIP_OR_DIMM                    : string;
        RDIMM_CONFIG_BITS               : string;

        -- setup / algorithm information
        NOM_DQS_PHASE_SETTING          : natural;
        SCAN_CLK_DIVIDE_BY             : natural;
        RDP_ADDR_WIDTH                 : natural;
        PLL_STEPS_PER_CYCLE            : natural;
        IOE_PHASES_PER_TCK             : natural;
        IOE_DELAYS_PER_PHS             : natural;
        MEM_IF_CLK_PS                  : natural;

        WRITE_DESKEW_T10               : natural;
        WRITE_DESKEW_HC_T10            : natural;
        WRITE_DESKEW_T9NI              : natural;
        WRITE_DESKEW_HC_T9NI           : natural;
        WRITE_DESKEW_T9I               : natural;
        WRITE_DESKEW_HC_T9I            : natural;
        WRITE_DESKEW_RANGE             : natural;

        -- initial mode register settings
        PHY_DEF_MR_1ST                 : natural;
        PHY_DEF_MR_2ND                 : natural;
        PHY_DEF_MR_3RD                 : natural;
        PHY_DEF_MR_4TH                 : natural;

        MEM_IF_DQSN_EN                 : natural;      -- default off for Cyclone-III
        MEM_IF_DQS_CAPTURE_EN          : natural;

        GENERATE_ADDITIONAL_DBG_RTL    : natural;      -- 1 signals to include iram and mmi blocks and 0 not to include

        SINGLE_DQS_DELAY_CONTROL_CODE  : natural;      -- reserved for future use
        PRESET_RLAT                    : natural;      -- reserved for future use
        EN_OCT                         : natural;      -- Does the sequencer use OCT during calibration.
        OCT_LAT_WIDTH                  : natural;
        SIM_TIME_REDUCTIONS            : natural;      -- if 0 null, if 2 rrp for 1 dqs group and 1 cs
        FORCE_HC                       : natural;      -- Use to force HardCopy in simulation.
        CAPABILITIES                   : natural;       -- advertise capabilities i.e. which ctrl block states to execute (default all on)
        TINIT_TCK                      : natural;
        TINIT_RST                      : natural;
        GENERATE_TRACKING_PHASE_STORE  : natural;      -- reserved for future use
        IP_BUILDNUM                    : natural
    );
    port (
        -- clk / reset
        clk                            : in    std_logic;
        rst_n                          : in    std_logic;

        -- calibration status and prompt
        ctl_recalibrate_req            : in    std_logic;

        -- the following two signals are reserved for future use
        ctl_cal_byte_lanes             : in    std_logic_vector(MEM_IF_NUM_RANKS * MEM_IF_DQS_WIDTH      - 1 downto 0);


        -- scanchain associated signals (reserved for future use)
        hr_rsc_clk                     : in    std_logic;

        -- address / command interface (note these are mapped internally to the seq_ac record)
        seq_ac_addr                    : out   std_logic_vector((DWIDTH_RATIO/2) * MEM_IF_ADDR_WIDTH     - 1 downto 0);
        seq_ac_ba                      : out   std_logic_vector((DWIDTH_RATIO/2) * MEM_IF_BANKADDR_WIDTH - 1 downto 0);
        seq_ac_cas_n                   : out   std_logic_vector((DWIDTH_RATIO/2)                         - 1 downto 0);
        seq_ac_ras_n                   : out   std_logic_vector((DWIDTH_RATIO/2)                         - 1 downto 0);
        seq_ac_we_n                    : out   std_logic_vector((DWIDTH_RATIO/2)                         - 1 downto 0);
        seq_ac_cke                     : out   std_logic_vector((DWIDTH_RATIO/2) * MEM_IF_NUM_RANKS      - 1 downto 0);
        seq_ac_cs_n                    : out   std_logic_vector((DWIDTH_RATIO/2) * MEM_IF_NUM_RANKS      - 1 downto 0);
        seq_ac_odt                     : out   std_logic_vector((DWIDTH_RATIO/2) * MEM_IF_NUM_RANKS      - 1 downto 0);
        seq_ac_rst_n                   : out   std_logic_vector((DWIDTH_RATIO/2)                         - 1 downto 0);
        seq_ac_sel                     : out   std_logic;
        seq_ac_add_1t_ac_lat_internal  : out   std_logic

    );
end entity;

library work;

-- The record_package (alt_mem_phy_record_pkg) is used to combine command and status signals
-- (into records) to be passed between sequencer blocks. It also contains type and record definitions
-- for the stages of DRAM memory calibration.
--
use work.ddr2_phy_alt_mem_phy_record_pkg.all;

-- The registers_package (alt_mem_phy_regs_pkg) is used to combine the definition of the
-- registers for the mmi status registers and functions/procedures applied to the registers
--
use work.ddr2_phy_alt_mem_phy_regs_pkg.all;

-- The constant_package (alt_mem_phy_constants_pkg) contains global 'constants' which are fixed
-- thoughout the sequencer and will not change (for constants which may change between sequencer
-- instances generics are used)
--
use work.ddr2_phy_alt_mem_phy_constants_pkg.all;

-- The iram address_package (alt_mem_phy_iram_addr_pkg) is used to define the base addresses used
-- for iram writes during calibration
--
use work.ddr2_phy_alt_mem_phy_iram_addr_pkg.all;

-- The address and command_package (alt_mem_phy_addr_cmd_pkg) is used to combine DRAM address
-- and command signals in one record and unify the functions operating on this record.
--
use work.ddr2_phy_alt_mem_phy_addr_cmd_pkg.all;


-- Individually include each of library files for the sub-blocks of the sequencer:
--
use work.ddr2_phy_alt_mem_phy_admin_nocalib;
--
--use work.ddr2_phy_alt_mem_phy_mmi;
--
--use work.ddr2_phy_alt_mem_phy_iram;
--
use work.ddr2_phy_alt_mem_phy_dgrb_nocalib;
--
use work.ddr2_phy_alt_mem_phy_dgwb_nocalib;
--
use work.ddr2_phy_alt_mem_phy_ctrl_nocalib;

--
architecture struct of ddr2_phy_alt_mem_phy_seq_nocalib IS

    attribute altera_attribute : string;
    attribute altera_attribute of struct : architecture is "-name MESSAGE_DISABLE 18010";

    -- outputs from the dgrb to generate the above rsu_codvw_* signals and report status to the mmi
    signal dgrb_mmi                         : t_dgrb_mmi;

    -- admin to mmi interface
    signal regs_admin_ctrl_rec            : t_admin_ctrl;  -- mmi register settings information
    signal admin_regs_status_rec          : t_admin_stat;  -- admin status information

    -- odt enable from the admin block based on mr settings
    signal enable_odt                     : std_logic;

    -- iram status information (sent to the ctrl block)
    signal iram_status                    : t_iram_stat;

    -- dgrb iram write interface
    signal dgrb_iram                      : t_iram_push;

    -- ctrl to iram interface
    signal ctrl_idib_top                  : natural;              -- current write location in the iram
    signal ctrl_active_block              : t_ctrl_active_block;
    signal ctrl_iram_push                 : t_ctrl_iram;
    signal iram_push_done                 : std_logic;
    signal ctrl_iram_ihi_write            : std_logic;

    -- local copies of calibration status
    signal ctl_init_success_int           : std_logic;
    signal ctl_init_fail_int              : std_logic;

    -- refresh period failure flag
    signal trefi_failure                  : std_logic;

    -- unified ctrl signal broadcast to all blocks from the ctrl block
    signal ctrl_broadcast                 : t_ctrl_command;

    -- standardised status report per block to control block
    signal admin_ctrl                     : t_ctrl_stat;
    signal dgwb_ctrl                      : t_ctrl_stat;
    signal dgrb_ctrl                      : t_ctrl_stat;

    -- mmi and ctrl block interface
    signal mmi_ctrl                       : t_mmi_ctrl;
    signal ctrl_mmi                       : t_ctrl_mmi;

    -- write datapath override signals
    signal dgwb_wdp_override              : std_logic;
    signal dgrb_wdp_override              : std_logic;

    -- address/command access request and grant between the dgrb/dgwb blocks and the admin block
    signal dgb_ac_access_gnt              : std_logic;
    signal dgb_ac_access_gnt_r            : std_logic;
    signal dgb_ac_access_req              : std_logic;
    signal dgwb_ac_access_req             : std_logic;

    -- per block address/command record (multiplexed in this_entity)
    signal admin_ac                       : t_addr_cmd_vector(0 to (DWIDTH_RATIO/2)-1);
    signal dgwb_ac                        : t_addr_cmd_vector(0 to (DWIDTH_RATIO/2)-1);
    signal dgrb_ac                        : t_addr_cmd_vector(0 to (DWIDTH_RATIO/2)-1);


    -- local copy of interface to inc/dec latency on  and postamble
    signal seq_rdata_valid_lat_dec_int    : std_logic;
    signal seq_rdata_valid_lat_inc_int    : std_logic;

    -- parameterisation of dgrb / dgwb / admin blocks from mmi register settings
    signal parameterisation_rec           : t_algm_paramaterisation;

    -- PLL reconfig
    signal dgrb_pll_inc_dec_n             : std_logic;
    signal dgrb_pll_start_reconfig        : std_logic;
    signal dgrb_pll_select                : std_logic_vector(CLOCK_INDEX_WIDTH - 1 downto 0);
    signal dgrb_phs_shft_busy             : std_logic;
    signal mmi_pll_inc_dec_n              : std_logic;
    signal mmi_pll_start_reconfig         : std_logic;
    signal mmi_pll_select                 : std_logic_vector(CLOCK_INDEX_WIDTH - 1 downto 0);
    signal pll_mmi                        : t_pll_mmi;
    signal mmi_pll                        : t_mmi_pll_reconfig;


    -- address and command 1t setting (unused for Full Rate)
    signal int_ac_nt                      : std_logic_vector(((DWIDTH_RATIO+2)/4) - 1 downto 0);
    signal dgrb_ctrl_ac_nt_good           : std_logic;

    -- the following signals are reserved for future use
    signal ctl_cal_byte_lanes_r           : std_logic_vector(ctl_cal_byte_lanes'range);
    signal mmi_setup                      : t_ctrl_cmd_id;
    signal dgwb_iram                      : t_iram_push;

    -- track number of poa / rdv adjustments (reporting only)
    signal poa_adjustments                : natural;
    signal rdv_adjustments                : natural;

    -- convert input generics from natural to std_logic_vector
    constant c_phy_def_mr_1st_sl_vector   : std_logic_vector(15 downto 0)   := std_logic_vector(to_unsigned(PHY_DEF_MR_1ST, 16));
    constant c_phy_def_mr_2nd_sl_vector   : std_logic_vector(15 downto 0)   := std_logic_vector(to_unsigned(PHY_DEF_MR_2ND, 16));
    constant c_phy_def_mr_3rd_sl_vector   : std_logic_vector(15 downto 0)   := std_logic_vector(to_unsigned(PHY_DEF_MR_3RD, 16));
    constant c_phy_def_mr_4th_sl_vector   : std_logic_vector(15 downto 0)   := std_logic_vector(to_unsigned(PHY_DEF_MR_4TH, 16));

    -- overrride on capabilities to speed up simulation time
    function capabilities_override(capabilities        : natural;
                                   sim_time_reductions : natural) return natural is
    begin
        if sim_time_reductions = 1 then
            return 2**c_hl_css_reg_cal_dis_bit; -- disable calibration completely
        else
            return capabilities;
        end if;
    end function;

    -- set sequencer capabilities
    constant c_capabilities_override      : natural                         := capabilities_override(CAPABILITIES, SIM_TIME_REDUCTIONS);
    constant c_capabilities               : std_logic_vector(31 downto 0)   := std_logic_vector(to_unsigned(c_capabilities_override,32));

    -- setup for address/command interface
    constant c_seq_addr_cmd_config        : t_addr_cmd_config_rec           := set_config_rec(MEM_IF_ADDR_WIDTH, MEM_IF_BANKADDR_WIDTH, MEM_IF_NUM_RANKS, DWIDTH_RATIO, MEM_IF_MEMTYPE);

    -- setup for odt signals
    -- odt setting as implemented in the altera high-performance controller for ddrx memories
    constant c_odt_settings               : t_odt_array(0 to MEM_IF_NUM_RANKS-1) := set_odt_values(MEM_IF_NUM_RANKS, MEM_IF_RANKS_PER_SLOT, MEM_IF_MEMTYPE);

    -- a prefix for all report signals to identify phy and sequencer block
--
    constant seq_report_prefix     : string  := "ddr2_phy_alt_mem_phy_seq_nocalib (top) : ";

    -- setup iram configuration
    constant c_iram_addresses             : t_base_hdr_addresses            := calc_iram_addresses(DWIDTH_RATIO, PLL_STEPS_PER_CYCLE, MEM_IF_DWIDTH, MEM_IF_NUM_RANKS, MEM_IF_DQS_CAPTURE_EN);
    constant c_int_iram_awidth            : natural                         := c_iram_addresses.required_addr_bits;

    constant c_tracking_interval_in_ms : natural := 128;
    constant c_mem_if_cal_bank         : natural := 0;      -- location to calibrate to
    constant c_mem_if_cal_base_col     : natural := 0;      -- default all zeros
    constant c_mem_if_cal_base_row     : natural := 0;
    constant c_non_op_eval_md          : string  := "PIN_FINDER";  -- non_operational evaluation mode (used when GENERATE_ADDITIONAL_DBG_RTL = 1)

begin  -- architecture struct

-- ---------------------------------------------------------------
-- tie off unused signals to default values
-- ---------------------------------------------------------------

    -- scan chain associated signals

    --
    admin: entity ddr2_phy_alt_mem_phy_admin_nocalib
        generic map
    (
        MEM_IF_DQS_WIDTH             => MEM_IF_DQS_WIDTH,
        MEM_IF_DWIDTH                => MEM_IF_DWIDTH,
        MEM_IF_DM_WIDTH              => MEM_IF_DM_WIDTH,
        MEM_IF_DQ_PER_DQS            => MEM_IF_DQ_PER_DQS,
        DWIDTH_RATIO                 => DWIDTH_RATIO,
        CLOCK_INDEX_WIDTH            => CLOCK_INDEX_WIDTH,
        MEM_IF_CLK_PAIR_COUNT        => MEM_IF_CLK_PAIR_COUNT,
        MEM_IF_ADDR_WIDTH            => MEM_IF_ADDR_WIDTH,
        MEM_IF_BANKADDR_WIDTH        => MEM_IF_BANKADDR_WIDTH,
        MEM_IF_NUM_RANKS             => MEM_IF_NUM_RANKS,
        ADV_LAT_WIDTH                => ADV_LAT_WIDTH,
        MEM_IF_DQSN_EN               => MEM_IF_DQSN_EN,
        MEM_IF_MEMTYPE               => MEM_IF_MEMTYPE,
        MEM_IF_CAL_BANK              => c_mem_if_cal_bank,
        MEM_IF_CAL_BASE_ROW          => c_mem_if_cal_base_row,
        GENERATE_ADDITIONAL_DBG_RTL  => GENERATE_ADDITIONAL_DBG_RTL,
        NON_OP_EVAL_MD               => c_non_op_eval_md,
        MEM_IF_CLK_PS                => MEM_IF_CLK_PS,
        TINIT_TCK                    => TINIT_TCK,
        TINIT_RST                    => TINIT_RST
    )
    port map
    (
        clk                          => clk,
        rst_n                        => rst_n,
        seq_ac                       => admin_ac,
        seq_ac_sel                   => seq_ac_sel,
        enable_odt                   => enable_odt,
        regs_admin_ctrl_rec          => regs_admin_ctrl_rec,
        admin_regs_status_rec        => admin_regs_status_rec,
        trefi_failure                => trefi_failure,
        ctrl_admin                   => ctrl_broadcast,
        admin_ctrl                   => admin_ctrl,
        ac_access_req                => dgb_ac_access_req,
        ac_access_gnt                => dgb_ac_access_gnt,
        cal_fail                     => ctl_init_fail_int,
        cal_success                  => ctl_init_success_int,
        ctl_recalibrate_req          => ctl_recalibrate_req
    );

    -- selectively include the debug i/f (iram and mmi blocks)
    with_debug_if : if GENERATE_ADDITIONAL_DBG_RTL = 1 generate

    signal mmi_iram                       : t_iram_ctrl;
    signal mmi_iram_enable_writes         : std_logic;
    signal rrp_mem_loc                    : natural range 0 to 2 ** c_int_iram_awidth - 1;
    signal command_req_r                  : std_logic;

    signal ctrl_broadcast_r               : t_ctrl_command;

    begin

    end generate;  -- with debug interface

    -- if no debug interface (iram/mmi block) tie off relevant signals
    without_debug_if : if GENERATE_ADDITIONAL_DBG_RTL = 0 generate

    constant c_slv_hl_stage_enable   : std_logic_vector(31 downto 0)                    := std_logic_vector(to_unsigned(c_capabilities_override, 32));
    constant c_hl_stage_enable       : std_logic_vector(c_hl_ccs_num_stages-1 downto 0) := c_slv_hl_stage_enable(c_hl_ccs_num_stages-1 downto 0);
    constant c_pll_360_sweeps        : natural                       := rrp_pll_phase_mult(DWIDTH_RATIO, MEM_IF_DQS_CAPTURE_EN);

    signal mmi_regs                  : t_mmi_regs := defaults;

    begin

        -- avalon interface signals

        -- The following registers are generated to simplify the assignments which follow
        -- but will be optimised away in synthesis
        mmi_regs.rw_regs    <= defaults(c_phy_def_mr_1st_sl_vector,
                                        c_phy_def_mr_2nd_sl_vector,
                                        c_phy_def_mr_3rd_sl_vector,
                                        c_phy_def_mr_4th_sl_vector,
                                        NOM_DQS_PHASE_SETTING,
                                        PLL_STEPS_PER_CYCLE,
                                        c_pll_360_sweeps,
                                        c_tracking_interval_in_ms,
                                        c_hl_stage_enable);

        mmi_regs.ro_regs    <= defaults(dgrb_mmi,
                                        ctrl_mmi,
                                        pll_mmi,
                                        mmi_regs.rw_regs.rw_if_test,
                                        '0',  -- do not use iram
                                        MEM_IF_DQS_CAPTURE_EN,
                                        int_ac_nt(0),
                                        trefi_failure,
                                        iram_status,
                                        c_int_iram_awidth);

        process(mmi_regs)
        begin
            --  debug parameterisation signals
            regs_admin_ctrl_rec          <= pack_record(mmi_regs.rw_regs);
            parameterisation_rec         <= pack_record(mmi_regs.rw_regs);
            mmi_pll                      <= pack_record(mmi_regs.rw_regs);
            mmi_ctrl                     <= pack_record(mmi_regs.rw_regs);
        end process;

        -- from the iram
        iram_status                      <= defaults;
        iram_push_done                   <= '0';

    end generate; -- without debug interface

    --
    dgrb : entity ddr2_phy_alt_mem_phy_dgrb_nocalib
        generic map(
        MEM_IF_DQS_WIDTH                 => MEM_IF_DQS_WIDTH,
        MEM_IF_DQ_PER_DQS			     => MEM_IF_DQ_PER_DQS,
        MEM_IF_DWIDTH                    => MEM_IF_DWIDTH,
        MEM_IF_DM_WIDTH                  => MEM_IF_DM_WIDTH,
        MEM_IF_DQS_CAPTURE               => MEM_IF_DQS_CAPTURE_EN,
        DWIDTH_RATIO                     => DWIDTH_RATIO,
        CLOCK_INDEX_WIDTH                => CLOCK_INDEX_WIDTH,
        MEM_IF_ADDR_WIDTH                => MEM_IF_ADDR_WIDTH,
        MEM_IF_BANKADDR_WIDTH            => MEM_IF_BANKADDR_WIDTH,
        MEM_IF_NUM_RANKS                 => MEM_IF_NUM_RANKS,
        MEM_IF_MEMTYPE                   => MEM_IF_MEMTYPE,
        ADV_LAT_WIDTH                    => ADV_LAT_WIDTH,
        PRESET_RLAT                      => PRESET_RLAT,
        PLL_STEPS_PER_CYCLE              => PLL_STEPS_PER_CYCLE,
        SIM_TIME_REDUCTIONS              => SIM_TIME_REDUCTIONS,
        GENERATE_ADDITIONAL_DBG_RTL      => GENERATE_ADDITIONAL_DBG_RTL,
        MEM_IF_CAL_BANK                  => c_mem_if_cal_bank,
        MEM_IF_CAL_BASE_COL              => c_mem_if_cal_base_col,
        EN_OCT                           => EN_OCT
   )
    port map(
        clk                              => clk,
        rst_n                            => rst_n,
        dgrb_ctrl                        => dgrb_ctrl,
        ctrl_dgrb                        => ctrl_broadcast,
        parameterisation_rec             => parameterisation_rec,
        phs_shft_busy                    => dgrb_phs_shft_busy,
        dgrb_iram                        => dgrb_iram,
        iram_push_done                   => iram_push_done,
        dgrb_ac                          => dgrb_ac,
        dgrb_ac_access_gnt               => dgb_ac_access_gnt_r,
        dgrb_wdp_ovride                  => dgrb_wdp_override,
        ctl_cal_byte_lanes               => ctl_cal_byte_lanes_r,
        odt_settings                     => c_odt_settings,
        dgrb_ctrl_ac_nt_good             => dgrb_ctrl_ac_nt_good,
        dgrb_mmi                         => dgrb_mmi
    );

    --
    dgwb : entity ddr2_phy_alt_mem_phy_dgwb_nocalib
        generic map(
        -- Physical IF width definitions
        MEM_IF_DQS_WIDTH             => MEM_IF_DQS_WIDTH,
        MEM_IF_DQ_PER_DQS			 => MEM_IF_DQ_PER_DQS,
        MEM_IF_DWIDTH                => MEM_IF_DWIDTH,
        MEM_IF_DM_WIDTH              => MEM_IF_DM_WIDTH,
        DWIDTH_RATIO                 => DWIDTH_RATIO,
        MEM_IF_ADDR_WIDTH            => MEM_IF_ADDR_WIDTH,
        MEM_IF_BANKADDR_WIDTH        => MEM_IF_BANKADDR_WIDTH,
        MEM_IF_NUM_RANKS             => MEM_IF_NUM_RANKS,
        MEM_IF_MEMTYPE               => MEM_IF_MEMTYPE,
        ADV_LAT_WIDTH                => ADV_LAT_WIDTH,
        MEM_IF_CAL_BANK              => c_mem_if_cal_bank,
        MEM_IF_CAL_BASE_COL          => c_mem_if_cal_base_col
   )
    port map(
        clk                          => clk,
        rst_n                        => rst_n,
        parameterisation_rec         => parameterisation_rec,
        dgwb_ctrl                    => dgwb_ctrl,
        ctrl_dgwb                    => ctrl_broadcast,
        dgwb_iram                    => dgwb_iram,
        iram_push_done               => iram_push_done,
        dgwb_ac_access_req           => dgwb_ac_access_req,
        dgwb_ac_access_gnt           => dgb_ac_access_gnt_r,
        dgwb_wdp_ovride              => dgwb_wdp_override,
        dgwb_ac                      => dgwb_ac,
        bypassed_rdata               => std_logic_vector(to_unsigned(0, 32)),--rdata(DWIDTH_RATIO * MEM_IF_DWIDTH -1 downto (DWIDTH_RATIO-1) * MEM_IF_DWIDTH),
        odt_settings                 => c_odt_settings
    );

    --
    ctrl: entity ddr2_phy_alt_mem_phy_ctrl_nocalib
        generic map(
        FAMILYGROUP_ID               => FAMILYGROUP_ID,
        MEM_IF_DLL_LOCK_COUNT        => 1280/(DWIDTH_RATIO/2),
        MEM_IF_MEMTYPE               => MEM_IF_MEMTYPE,
        DWIDTH_RATIO                 => DWIDTH_RATIO,
        IRAM_ADDRESSING              => c_iram_addresses,
        MEM_IF_CLK_PS                => MEM_IF_CLK_PS,
        TRACKING_INTERVAL_IN_MS      => c_tracking_interval_in_ms,
        GENERATE_ADDITIONAL_DBG_RTL  => GENERATE_ADDITIONAL_DBG_RTL,
        MEM_IF_NUM_RANKS             => MEM_IF_NUM_RANKS,
        MEM_IF_DQS_WIDTH             => MEM_IF_DQS_WIDTH,
        SIM_TIME_REDUCTIONS          => SIM_TIME_REDUCTIONS,
        ACK_SEVERITY                 => warning
    )
    port map(
        clk                          => clk,
        rst_n                        => rst_n,
        ctl_init_success             => ctl_init_success_int,
        ctl_init_fail                => ctl_init_fail_int,
        ctl_recalibrate_req          => ctl_recalibrate_req,
        iram_status                  => iram_status,
        iram_push_done               => iram_push_done,
        ctrl_op_rec                  => ctrl_broadcast,
        admin_ctrl                   => admin_ctrl,
        dgrb_ctrl                    => dgrb_ctrl,
        dgwb_ctrl                    => dgwb_ctrl,
        ctrl_iram_push               => ctrl_iram_push,
        ctl_cal_byte_lanes           => ctl_cal_byte_lanes_r,
        dgrb_ctrl_ac_nt_good         => dgrb_ctrl_ac_nt_good,
        int_ac_nt                    => int_ac_nt,
        mmi_ctrl                     => mmi_ctrl,
        ctrl_mmi                     => ctrl_mmi
    );


-- ---------------------------------------------------------------
-- top level multiplexing and ctrl functionality
-- ---------------------------------------------------------------


    ac_mux : block

        constant c_mem_clk_disable_pipe_len : natural := 3;


        signal seen_phy_init_complete  : std_logic;
        signal mem_clk_disable         : std_logic_vector(c_mem_clk_disable_pipe_len - 1 downto 0);

        signal ctrl_broadcast_r        : t_ctrl_command;

    begin

        -- register ctrl_broadcast locally
        -- #for speed and to reduce fan out
        process (clk, rst_n)
         begin
            if rst_n = '0' then
                ctrl_broadcast_r <= defaults;
            elsif rising_edge(clk) then
                ctrl_broadcast_r <= ctrl_broadcast;
            end if;
         end process;

        -- multiplex mem interface control between admin, dgrb and dgwb
        process(clk, rst_n)
        begin
            if rst_n = '0' then


                mem_clk_disable         <= (others => '1');
                seen_phy_init_complete  <= '0';

                seq_ac_addr      <= (others => '0');
                seq_ac_ba        <= (others => '0');
                seq_ac_cas_n     <= (others => '1');
                seq_ac_ras_n     <= (others => '1');
                seq_ac_we_n      <= (others => '1');
                seq_ac_cke       <= (others => '0');
                seq_ac_cs_n      <= (others => '1');
                seq_ac_odt       <= (others => '0');
                seq_ac_rst_n     <= (others => '0');

            elsif rising_edge(clk) then

                mem_clk_disable(c_mem_clk_disable_pipe_len-1 downto 1) <= mem_clk_disable(c_mem_clk_disable_pipe_len-2 downto 0);

                if ctl_recalibrate_req = '1' then
                    mem_clk_disable(0)     <= '1';
                    seen_phy_init_complete <= '0';
                elsif ctrl_broadcast_r.command = cmd_init_dram and ctrl_broadcast_r.command_req = '1' then
                    mem_clk_disable(0)     <= '0';
                    seen_phy_init_complete <= '1';
                end if;

                if seen_phy_init_complete /= '1' then -- if not initialised the phy hold in reset

                    seq_ac_addr      <= (others => '0');
                    seq_ac_ba        <= (others => '0');
                    seq_ac_cas_n     <= (others => '1');
                    seq_ac_ras_n     <= (others => '1');
                    seq_ac_we_n      <= (others => '1');
                    seq_ac_cke       <= (others => '0');
                    seq_ac_cs_n      <= (others => '1');
                    seq_ac_odt       <= (others => '0');
                    seq_ac_rst_n     <= (others => '0');

                else

                    unpack_addr_cmd_vector (
                        c_seq_addr_cmd_config,
                        admin_ac,--v_seq_ac_mux,
                        seq_ac_addr,
                        seq_ac_ba,
                        seq_ac_cas_n,
                        seq_ac_ras_n,
                        seq_ac_we_n,
                        seq_ac_cke,
                        seq_ac_cs_n,
                        seq_ac_odt,
                        seq_ac_rst_n);

                end if;

            end if;
        end process;

    end block;

    -- register dgb_ac_access_gnt signal to ensure ODT set correctly in dgrb and dgwb prior to a read or write operation
    process(clk, rst_n)
    begin
        if rst_n = '0' then
            dgb_ac_access_gnt_r <= '0';
        elsif rising_edge(clk) then
            dgb_ac_access_gnt_r <= dgb_ac_access_gnt;
        end if;
    end process;

    -- multiplex access request from dgrb/dgwb to admin block with checking for multiple accesses
    process (dgwb_ac_access_req)
    begin
        dgb_ac_access_req <= '0';
        if dgwb_ac_access_req = '1' then
            dgb_ac_access_req <= '1';
        end if;
    end process;


    -- register 1t addr/cmd and odt latency outputs
    process(clk, rst_n)
    begin
        if rst_n = '0' then
            seq_ac_add_1t_ac_lat_internal  <= '0';
        elsif rising_edge(clk) then
            seq_ac_add_1t_ac_lat_internal  <= int_ac_nt(0);
        end if;
    end process;



end architecture struct;
